home *** CD-ROM | disk | FTP | other *** search
/ Scene Storm / Scene Storm - Volume 1.iso / coding / c / pdc / dasm / convert.c next >
Encoding:
C/C++ Source or Header  |  1990-04-19  |  11.8 KB  |  483 lines

  1.  
  2. struct instruction {
  3.   unsigned opcode:  4;
  4.   unsigned destreg: 3;
  5.   unsigned extend:  3;
  6.   unsigned srcmode: 3;
  7.   unsigned srcreg:  3;
  8.   };
  9.  
  10. struct shiftbits {
  11.   unsigned opcode:  4;
  12.   unsigned count:   3;
  13.   unsigned direct:  1;
  14.   unsigned optype:  2;
  15.   unsigned opmode:  1;
  16.   unsigned shift:   2;
  17.   unsigned dest:    3;
  18.   };
  19.  
  20. struct testbits {
  21.   unsigned opcode:  4;
  22.   unsigned ccode:   4;
  23.   unsigned offset:  8;
  24.   };
  25.  
  26. union {
  27.   struct instruction iview;
  28.   struct shiftbits s;
  29.   struct testbits tview;
  30.   short sview; } cheat;
  31.  
  32. char opline[120], *opp, *valp;
  33.  
  34. startline()
  35. {
  36.   valp=opline; opp=opline+34;
  37. }
  38.  
  39. displayline()
  40. {
  41.   while (valp<(opline+34)) *valp++=' ';
  42.   *opp='\0';
  43.   printf("%s\n",opline);
  44. }
  45.  
  46. padd()
  47. {
  48.   while (opp<(opline+42)) opchar(' ');
  49. }
  50.  
  51. opchar(c)
  52. char c;
  53. {
  54.   *opp++=c;
  55. }
  56.  
  57. opstring(s)
  58. char *s;
  59. {
  60.   while (*s!='\0') *opp++=*s++;
  61. }
  62.  
  63. opcode(s)
  64. char *s;
  65. {
  66.   int n=5;
  67.   while (*s!='\0' & n-- >0) *opp++=*s++;
  68. }
  69.  
  70. opint(v)
  71. int v;
  72. {
  73.   int t;
  74.   if (v<=0) *opp++='0';
  75.   else { if ((t=v/10)>0) opint(t); *opp++ = v%10+'0'; };
  76. }
  77.  
  78. ophex(v,n)
  79. int v,n;
  80. {
  81.   char c;
  82.   while (n-- > 0)
  83.     *opp++ = (c=(v>>(n<<2)) & 0xF) <= 9 ? c+'0' : c-10+'A';
  84. }
  85.  
  86. lefthex(v,b)
  87. int v,b;
  88. {
  89.   int n=4;
  90.   char c;
  91.   while (b-->0) *valp++ = ' ';
  92.   while (n-->0)
  93.     *valp++ = (c=(v>>(n<<2)) & 0xF) <= 9 ?c+'0':c-10+'A';
  94. }
  95.  
  96. mynext(b)
  97. int b;
  98. {
  99.   int v;
  100.   lefthex(v=nextcodeword(),b);
  101.   return v;
  102. }
  103.  
  104. invalid()
  105. {
  106.   opstring(".WORD"); padd(); ophex(cheat.sview,4);
  107. }
  108.  
  109. int srckind;
  110.  
  111. sourcekind(k)
  112. int k;
  113. {
  114.   opchar('.');
  115.   switch (k) {
  116.     case 0: case 4:         opchar('B'); srckind=0; break;
  117.     case 1: case 5: case 3: opchar('W'); srckind=1; break;
  118.     case 2: case 6: case 7: opchar('L'); srckind=2; break;
  119.     }
  120. }
  121.  
  122. shiftinstruction()
  123. {
  124.   int t;
  125.   static char *mnemonics[8] =
  126.        { "ASR",  "ASL",  "LSR", "LSL",
  127.          "ROXR", "ROXL", "ROR", "ROL" };
  128.   if (cheat.s.optype==3) {
  129.     opstring(mnemonics[(cheat.s.count<<1)+cheat.s.direct]);
  130.     padd();
  131.     operand(cheat.iview.srcmode,cheat.iview.srcreg);
  132.     }
  133.   else {
  134.     opstring(mnemonics[(cheat.s.shift<<1)+cheat.s.direct]);
  135.     sourcekind(cheat.s.optype);
  136.     padd();
  137.     if (cheat.s.opmode==0) {
  138.       opchar('#');
  139.       opint( (t=cheat.s.count)==0 ? 8 : t );
  140.       }
  141.     else
  142.       operand(0,cheat.s.count);
  143.     opchar(',');
  144.     operand(0,cheat.s.dest);
  145.     }
  146. }
  147.  
  148. operand(mode,reg)
  149. int mode,reg;
  150. {
  151.   struct indexword {
  152.     unsigned dora :1;
  153.     unsigned ireg :3;
  154.     unsigned size :1;
  155.     unsigned junk :3;
  156.     unsigned disp :8;
  157.     };
  158.   union {
  159.     short sh;
  160.     struct indexword ind;
  161.     } mycheat;
  162.   switch (mode) {
  163.     case 0: opchar('D'); opint(reg); break;
  164.     case 1: opchar('A'); opint(reg); break;
  165.     case 2: opstring("(A"); opint(reg); opchar(')'); break;
  166.     case 3: opstring("(A"); opint(reg); opstring(")+");
  167.             break;
  168.     case 4: opstring("-(A"); opint(reg); opchar(')'); break;
  169.     case 5: ophex(mynext(1),4);
  170.             opstring("(A"); opint(reg); opchar(')'); break;
  171.     case 6: mycheat.sh=mynext(1);
  172.             ophex(mycheat.ind.disp,2);
  173.             opstring("(A"); opint(reg); opchar(',');
  174.             opchar(mycheat.ind.dora==0 ? 'D' : 'A');
  175.             opint(mycheat.ind.ireg);
  176.             opchar('.');
  177.             opchar(mycheat.ind.size==0 ? 'W' : 'L');
  178.             opchar(')'); break;
  179.     case 7: switch (reg) {
  180.       case 0: ophex(mynext(1),4); break;
  181.       case 1: ophex(mynext(1),4); ophex(mynext(0),4); break;
  182.       case 2: opchar('+'); ophex(mynext(1),4); break;
  183.       case 3: mycheat.sh=mynext(1);
  184.               opchar('+');
  185.               ophex(mycheat.ind.disp,2);
  186.               opchar('(');
  187.               opchar(mycheat.ind.dora==0 ? 'D' : 'A');
  188.               opint(mycheat.ind.ireg);
  189.               opchar('.');
  190.               opchar(mycheat.ind.size==0 ? 'W' : 'L');
  191.               opchar(')');
  192.               break;
  193.       case 4: opchar('#');
  194.               switch (srckind) {
  195.                 case 0: ophex(mynext(1),2); break;
  196.                 case 1: ophex(mynext(1),4); break;
  197.                 case 2: ophex(mynext(1),4); ophex(mynext(0),4); break;
  198.                 };
  199.               break;
  200.       }
  201.     }
  202. }
  203.  
  204. conditioncode(cc)
  205. int cc;
  206. {
  207.   char *codes = "RASRHILSCCCSNEEQVCVSPLMIGELTGTLE";
  208.   if (cc>1 || cheat.iview.opcode==6) {
  209.     opchar(codes[cc<<1]);
  210.     opchar(codes[(cc<<1)+1]);
  211.     }
  212.   else if (cc==0) opchar('T'); else opchar('F');
  213. }
  214.  
  215. handlezero()
  216. {
  217.   int ext =  cheat.iview.extend;
  218.   int dreg = cheat.iview.destreg;
  219.   int smod = cheat.iview.srcmode;
  220.   int sreg = cheat.iview.srcreg;
  221.   static char *opzero[] = {"OR","AND","SUB","ADD","","EOR","CMP",""};
  222.   static char *opone[] = {"BTST","BCHG","BCLR","BSET"};
  223.   if (ext<=2 & dreg!=4) {
  224.     opstring(opzero[dreg]); sourcekind(ext); padd();
  225.     operand(7,4); opchar(',');
  226.     if (smod==7 && sreg==4)
  227.       if (srckind==0) opstring("CCR"); else opstring("SR");
  228.     else operand(smod,sreg);
  229.     }
  230.   else if (ext<=3 & dreg==4) {
  231.     opstring(opone[ext]); padd();
  232.     srckind = 0; operand(7,4); opchar(','); operand(smod,sreg);
  233.     }
  234.   else if (ext>=4) {
  235.     if (smod!=1) {
  236.       opstring(opone[ext-4]); padd();
  237.       operand(0,dreg); opchar(','); operand(smod,sreg);
  238.       }
  239.     else {
  240.       opstring("MOVEP"); sourcekind(1+(ext&1)); padd();
  241.       if (ext<=5) {
  242.         operand(5,sreg); opchar(','); operand(0,dreg);
  243.         }
  244.       else {
  245.         operand(0,dreg); opchar(','); operand(5,sreg);
  246.         }
  247.       }
  248.     }
  249.   else opstring("Invalid");
  250. }
  251.  
  252. breakfurther(base)
  253. char *base;
  254. {
  255.   int ext =  cheat.iview.extend;
  256.   int dreg = cheat.iview.destreg;
  257.   int smod = cheat.iview.srcmode;
  258.   int sreg = cheat.iview.srcreg;
  259.   int comm,t;
  260.  
  261.   if ( ( (comm=*(base+ext)) & 0xF0 ) == 0x40 )
  262.     comm = *( base+(8+(t=comm&0xF)+(t<<2)+(smod==0 ? 1 :(smod==1 ? 2 : 0))));
  263.   if (comm==0)
  264.     opstring("Invalid");
  265.   else {
  266.     opcode(base+(8+(t=comm&7)+(t<<2)));
  267.     if (comm & 8) sourcekind(ext);
  268.     if ((t=(comm>>4)&0xF)>=13) conditioncode(cheat.tview.ccode);
  269.     padd();
  270.     switch (t) {
  271.       case 0: opstring("Invalid"); break;
  272.       case 1: operand(smod,sreg); opchar(','); operand(0,dreg); break;
  273.       case 2: operand(smod,sreg); opchar(','); operand(1,dreg); break;
  274.       case 3: operand(0,dreg); opchar(','); operand(smod,sreg); break;
  275.       case 4: opstring("Internal check fail"); break;
  276.       case 5: operand(3,sreg); opchar(','); operand(3,dreg); break;
  277.       case 6: operand(4,sreg); opchar(','); operand(4,dreg); break;
  278.       case 7: opchar('#'); opint(dreg); opchar(','); operand(smod,sreg);
  279.               break;
  280.       case 8: opchar('#'); ophex(cheat.tview.offset,2); opchar(',');
  281.               operand(0,dreg); break;
  282.       case 9: operand(1,dreg); opchar(','); operand(smod,sreg); break;
  283.       case 13: operand(smod,sreg); break;
  284.       case 14: operand(0,sreg); opchar(','); operand(7,2); break;
  285.       case 15: if (cheat.tview.offset==0)
  286.                  operand(7,2);
  287.                else {
  288.                  opchar('+');
  289.                  ophex(cheat.tview.offset,2);
  290.                  };
  291.                break;
  292.       }
  293.     }
  294. }
  295.  
  296. moveinstruction(kind)
  297. int kind;
  298. {
  299.   opstring("MOVE");
  300.   sourcekind(kind==1 ? 0 : (kind==2 ? 2 : 1));
  301.   padd();
  302.   operand(cheat.iview.srcmode,cheat.iview.srcreg);
  303.   opchar(',');
  304.   operand(cheat.iview.extend,cheat.iview.destreg);
  305. }
  306.  
  307. startrange(bit)
  308. int bit;
  309. {
  310.   operand(bit<=7 ? 0 : 1, bit%8);
  311. }
  312.  
  313. endrange(first,bit)
  314. int first,bit;
  315. {
  316.   if (first<=7 && bit>7) {
  317.     endrange(first,7);
  318.     opchar('/');
  319.     startrange(8);
  320.     first=8;
  321.     };
  322.   if (bit>first) {
  323.     opchar('-');
  324.     startrange(bit);
  325.     }
  326. }
  327.  
  328. registerlist(kkkk,mask)
  329. int kkkk,mask;
  330. {
  331.   int bit=0; int inrange=-1; int some=0;
  332.   while (bit <= 15) {
  333.     if ( ( kkkk ? (mask>>(15-bit)) : (mask>>bit) ) & 1 ) {
  334.       if (inrange<0) {
  335.         if (some) opchar('/');
  336.         startrange(bit);
  337.         some=1; inrange=bit;
  338.         }
  339.       }
  340.     else {
  341.       if (inrange>=0) {
  342.         endrange(inrange,bit-1);
  343.         inrange=-1;
  344.         }
  345.       };
  346.     bit++;
  347.     };
  348.   if (inrange>=0) endrange(inrange,15);
  349. }
  350.  
  351. specialbits()
  352. {
  353.   int smod = cheat.iview.srcmode;
  354.   int sreg = cheat.iview.srcreg;
  355.   switch (smod) {
  356.     case 0: opstring("TRAP"); padd(); opchar('#'); opint(sreg); break;
  357.     case 1: opstring("Invalid"); break;
  358.     case 2: opstring("LINK"); padd(); operand(1,sreg);
  359.             opchar(','); srckind=1; operand(7,4); break;
  360.     case 3: opstring("UNLK"); padd(); operand(1,sreg); break;
  361.     case 4: opstring("MOVE"); padd(); operand(1,sreg);
  362.                                       opstring(",USP"); break;
  363.     case 5: opstring("MOVE"); padd(); opstring("USP,");
  364.                                       operand(1,sreg); break;
  365.     case 6: switch (sreg) {
  366.       case 0: opstring("RESET"); break;
  367.       case 1: opstring("NOP"); break;
  368.       case 2: opstring("STOP"); padd(); srckind=1; operand(7,4); break;
  369.       case 3: opstring("RTE"); break;
  370.       case 4: opstring("Invalid"); break;
  371.       case 5: opstring("RTS"); break;
  372.       case 6: opstring("TRAPV"); break;
  373.       case 7: opstring("RTR"); break;
  374.       }; break;
  375.     case 7: opstring("Invalid"); break;
  376.     }
  377. }
  378.  
  379. handlefour()
  380. {
  381.   int ext =  cheat.iview.extend;
  382.   int dreg = cheat.iview.destreg;
  383.   int smod = cheat.iview.srcmode;
  384.   int sreg = cheat.iview.srcreg;
  385.   int reglist;
  386.   static char *unaryA[] = {"NEGX","CLR","NEG","NOT","","TST"};
  387.   static char *cross4[] = {"NBCD","PEA", "MOVEM.W","MOVEM.L",
  388.                            "NBCD","SWAP","EXT.W",  "EXT.L"};
  389.   static char *jumps[] = {"JSR","JMP"};
  390.  
  391.   if (ext<=2 && (dreg<=3 || dreg==5)) {
  392.     opstring(unaryA[dreg]); sourcekind(ext); padd(); operand(smod,sreg);
  393.     }
  394.   else if (dreg==4 && ext<=3) {
  395.     opstring(cross4[smod==0 ? ext+4 : ext]); padd();
  396.     if (ext>=2 && smod!=0) {
  397.       registerlist(smod==4,mynext(1)); opchar(',');
  398.       };
  399.     operand(smod,sreg);
  400.     }
  401.   else if (ext==2 || ext==3) {
  402.     if (dreg==6) {
  403.       opstring(cross4[ext]); padd(); reglist=mynext(1);
  404.       operand(smod==4 ? 3: smod ,sreg); opchar(','); registerlist(0,reglist);
  405.       }
  406.     else if (dreg==7) {
  407.       opstring(jumps[ext-2]); padd(); operand(smod,sreg);
  408.       }
  409.     else if (ext==3) {
  410.       switch (dreg) {
  411.         case 0: opstring("MOVE"); padd(); opstring("SR,");
  412.                 operand(smod,sreg); break;
  413.         case 1: opstring("Invalid"); break;
  414.         case 2: opstring("MOVE"); padd(); srckind=0;
  415.                 operand(smod,sreg); opstring(",CCR"); break;
  416.         case 3: opstring("MOVE"); padd(); srckind=1;
  417.                 operand(smod,sreg); opstring(",SR");  break;
  418.         case 5: opstring("TAS"); padd(); operand(smod,sreg); break;
  419.         }
  420.       }
  421.     }
  422.   else if (ext==7) {
  423.     opstring("LEA"); padd(); operand(smod,sreg);
  424.     opchar(','); operand(1,dreg);
  425.     }
  426.   else if (ext==6) {
  427.     opstring("CHK"); padd(); srckind=1;
  428.     operand(smod,sreg); opchar(','); operand(0,dreg);
  429.     }
  430.   else if (ext==1 && dreg==7) specialbits();
  431.   else opstring("Invalid");
  432. }
  433.  
  434. char *interpret[16] = {
  435. /*0*/ "\0\0\0\0\0\0\0\0",
  436. /*1*/ "",
  437. /*2*/ "",
  438. /*3*/ "",
  439. /*4*/ "\0\0\0\0\0\0\0\0",
  440. /*5*/ "\170\170\170\104\173\173\173\104ADDQ\0S\0\0\0\0DB\0\0\0SUBQ\0\321\321\342",
  441. /*6*/ "\360\360\360\360\360\360\360\360B",
  442. /*7*/ "\200\200\200\200\200\200\200\200MOVEQ",
  443. /*8*/ "\30\30\30\21\104\105\105\22OR\0\0\0DIVU\0DIVS\0SBCD\0\70\23\143\0\0\70\0\0",
  444. /*9*/ "\30\30\30\50\102\102\102\50SUB\0\0SUBX\0\70\31\151",
  445. /*a*/ "\0\0\0\0\0\0\0\0",
  446. /*b*/ "\30\30\30\50\103\103\103\50CMP\0\0EOR\0\0CMPM\0\71\71\132",
  447. /*c*/ "\30\30\30\21\105\106\107\22AND\0\0MULU\0MULS\0ABCD\0EXG\0\0\70\23\143\0\0\70\64\224\0\0\70\0\64",
  448. /*d*/ "\30\30\30\50\102\102\102\50ADD\0\0ADDX\0\70\31\151",
  449. /*e*/ "",
  450. /*f*/ "\0\0\0\0\0\0\0\0"
  451.   };
  452.  
  453.  
  454.  
  455.     decode(addr)
  456.  
  457. int addr;
  458.  
  459. {
  460.   startline();
  461.   lefthex(addr>>16,0); lefthex(addr,0);
  462.   cheat.sview=mynext(1);
  463.   switch (cheat.iview.opcode) {
  464.     case 1:
  465.     case 2:
  466.     case 3:  moveinstruction(cheat.iview.opcode); break;
  467.     case 0:  handlezero(); break;
  468.     case 4:  handlefour(); break;
  469.     case 5:
  470.     case 6:
  471.     case 7:
  472.     case 8:
  473.     case 9:
  474.     case 10:
  475.     case 11:
  476.     case 12:
  477.     case 13:
  478.     case 15: breakfurther(interpret[cheat.iview.opcode]); break;
  479.     case 14: shiftinstruction(); break;
  480.     };
  481.   displayline();
  482. }
  483.